package com.miplus.ccrm.core.service.sto;

import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.conditions.update.UpdateWrapper;
import com.github.yulichang.base.MPJBaseServiceImpl;
import com.github.yulichang.wrapper.MPJLambdaWrapper;
import com.miplus.ccrm.common.*;
import com.miplus.ccrm.core.controller.vo.ficase.ImpResultVo;
import com.miplus.ccrm.core.controller.vo.sto.*;
import com.miplus.ccrm.core.mapper.*;
import com.miplus.ccrm.core.pojo.*;
import com.miplus.ccrm.core.utils.EnumFiCaseQueue;
import com.miplus.ccrm.core.utils.EnumFiCaseStatus;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import javax.annotation.Resource;
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.LinkedList;
import java.util.List;
import java.util.stream.Collectors;

/**
* @author pc
* @description 针对表【credit_cockcollect】的数据库操作Service实现
* @createDate 2024-04-27 14:25:16
*/
@Slf4j
@Service
public class CreditCockcollectServiceImpl extends MPJBaseServiceImpl<CreditCockcollectMapper, CreditCockcollect>
    implements CreditCockcollectService{
    @Resource
    private ConCustomerMapper conCustomerMapper;
    @Resource
    private ConCustomertagMapper conCustomertagMapper;
    @Resource
    private ConContactMapper conContactMapper;
    @Resource
    private SysNamesMapper sysNamesMapper;
    @Resource
    private FiImportHistMapper fiImportHistMapper;
    @Resource
    private FiCreditcasesMapper fiCreditcasesMapper;

    @Override
    @Transactional
    public ImpResultVo impCockList(String $usrid, CockImpVo paras)
    {//批量增加（导入）命令催记
        SimpleDateFormat sdf=new SimpleDateFormat("yyMMddHHmmss");
        String batchid = "G"+sdf.format(new Date());

        int ret=0;
        ImpResultVo impResultVo=new ImpResultVo();
        List<String> fails=new LinkedList<>();
        log.info("impCockList:tempid={},batchid={},Count={}",
                paras.getTempid(),batchid,paras.getAddVoList().size()
        );
        for(CockAddVo fiAdd : paras.getAddVoList()){
            String contractno=fiAdd.getContractno();
            String custno=fiAdd.getCustNo();

            ConCustomer customer=conCustomerMapper.selectById(custno);
            if(customer==null){
                customer=new ConCustomer();
                customer.setOrigin("20"); //公鸡贷
                customer.setType(1); // 个人用户
                customer.setCustomernumber(custno);
                customer.setOpenacctcertno(fiAdd.getIdnumber());
                customer.setCorpname(fiAdd.getCorpname());
                customer.setCustacctorgno(fiAdd.getAcctorgno());
                customer.setCustname(fiAdd.getCustname());
                customer.setCreatedby($usrid);
                customer.setCreateddate(new Date());
                customer.setLastmodifiedby($usrid);
                customer.setLastmodifieddate(new Date());
                customer.setBatchid(batchid);
                if(JPubUtils.IsNotEmpty(fiAdd.getPhone())) {
                    customer.setCustphone(fiAdd.getPhone());
                }
                conCustomerMapper.insert(customer);
            }
            String phone=fiAdd.getPhone();
            if(JPubUtils.IsNotEmpty(phone)){
                AddContact($usrid,custno,fiAdd.getCustname(),fiAdd.getRelational(),fiAdd.getPhone());
            }
            phone=fiAdd.getPhone2();
            if(JPubUtils.IsNotEmpty(phone)){
                AddContact($usrid,custno,fiAdd.getCustname(),fiAdd.getRelational2(),phone);
            }
            phone=fiAdd.getPhone3();
            if(JPubUtils.IsNotEmpty(phone)){
                AddContact($usrid,custno,fiAdd.getCustname(),fiAdd.getRelational3(),phone);
            }

            CreditCockcollect cockcollect=baseMapper.selectById(contractno);
            if(cockcollect==null){
                cockcollect=new CreditCockcollect();
                cockcollect.setCrusr($usrid);
                cockcollect.setCrdt(new Date());
                cockcollect.setCustNo(custno);
                cockcollect.setContractno(contractno);
                cockcollect.setBatchid(batchid);
                baseMapper.insert(cockcollect);
            }
            else{
                //需要，否则就会设置2次属性了，PG会报错
                cockcollect=new CreditCockcollect();
            }
            cockcollect.setMdusr($usrid);
            cockcollect.setMddt(new Date());
            cockcollect.setBatchid(paras.getBatchid());
            baseMapper.update(cockcollect,new UpdateWrapper<CreditCockcollect>()
                    .lambda()
                    .eq(CreditCockcollect::getContractno,contractno)
                    .set(CreditCockcollect::getArea,fiAdd.getArea())
                    .set(JPubUtils.IsNotEmpty(fiAdd.getAccdodt()),CreditCockcollect::getAccdodt,JPubUtils.StringToDate(fiAdd.getAccdodt()))
                    .set(CreditCockcollect::getAcctorgno,fiAdd.getAcctorgno())
                    .set(CreditCockcollect::getCrdfee,fiAdd.getCrdfee())
                    .set(CreditCockcollect::getCrdprinold,fiAdd.getCrdprinold())
                    .set(CreditCockcollect::getCrdprin,fiAdd.getCrdprin())
                    .set(CreditCockcollect::getDebttotal,fiAdd.getDebttotal())
                    .set(CreditCockcollect::getAcctType, GetAccTypeID(fiAdd.getAcctType()))
                    .set(CreditCockcollect::getCorpname,fiAdd.getCorpname())
                    .set(CreditCockcollect::getRemark,fiAdd.getRemark())
            );
            ret++;
        }
        AddImportHist(batchid, paras.getBatchdsc(), $usrid,
                paras.getTempid(), paras.getFilename(), paras.getAddVoList().size(), ret);

        impResultVo.setBatchid(batchid);
        impResultVo.setOkcnt(ret);
        impResultVo.setFailcnt(fails.size());
        impResultVo.setFaillist(fails);
        return impResultVo;
    }

    private int AddContact(String $usrid,String custno,String custname,String relational,String phone)
    {
        Long num=conContactMapper.selectCount(new QueryWrapper<ConContact>()
                        .eq("customernumber",custno)
                        .eq("phone",phone)
                        .eq("origin","20")
        );
        if(num>0) return 0;

        relational=GetRelationID(relational);

        ConContact contact=new ConContact();
        contact.setCustomernumber(custno);

        if(JPubUtils.IsNotEmpty(relational)) {
            contact.setRelational(relational);
        }

        if(JPubUtils.IsNotEmpty(custname)&&JPubUtils.IsEqual(relational,"9")){
            //本人=9
            contact.setName(custname);
        }

        contact.setPhntype("03"); //移动电话
        contact.setPhone(phone);
        contact.setOrigin("20");
        contact.setCreatedby($usrid);
        contact.setCreateddate(new Date());
        contact.setLastmodifiedby($usrid);
        contact.setLastmodifieddate(new Date());
        return conContactMapper.insert(contact);
    }

    private String GetRelationID(String relational)
    {
        if(JPubUtils.IsEmpty(relational)) return "";
        try {
            SysNames names = sysNamesMapper.selectOne(new QueryWrapper<SysNames>()
                    .eq("tid", "CON.RELATION")
                    .eq("dsc", relational)
            );
            return names.getId();
        }
        catch (Exception e){
            log.warn("GetRelationID Err:{}",e.getMessage());
            return "";
        }
    }

    private String GetAccTypeID(String acctype)
    {
        if(JPubUtils.IsEmpty(acctype)) return "";
        try {
            SysNames names = sysNamesMapper.selectOne(new QueryWrapper<SysNames>()
                    .eq("tid", "CREDIT.ACCT.TYPE")
                    .eq("dsc", acctype)
            );
            return names.getId();
        }
        catch (Exception e){
            log.warn("GetAccTypeID Err:{}",e.getMessage());
            return "";
        }
    }

    private void AddImportHist(String batchid,String batchdsc,String $usrid,String tempid,String filename,int totlecnt,int okcnt)
    {
        FiImportHist fiImportHist=new FiImportHist();
        fiImportHist.setBatchid(batchid);
        fiImportHist.setBatchdesc(batchdsc);
        fiImportHist.setDotype("import");
        fiImportHist.setTempid(tempid);
        fiImportHist.setFilename(filename);
        fiImportHist.setDousr($usrid);
        fiImportHist.setDodt(new Date());
        fiImportHist.setTotalcnt(totlecnt);
        fiImportHist.setOkcnt(okcnt);
        fiImportHist.setStatus(1);
        fiImportHistMapper.insert(fiImportHist);
    }

    @Override
    @Transactional
    public CmdResVo CreateFiCase(String $usrid, CrtFiCaseVo crtFiCaseVo)
    {
        String batchid=crtFiCaseVo.getBatchid();
        List<CreditCockcollect> cockcollects=baseMapper.selectList(
                new QueryWrapper<CreditCockcollect>()
                        .eq("batchid",batchid)
        );

        log.info("Cock.CreateFiCase({}):count={}",batchid,cockcollects.size());

        if(JPubUtils.IsEmpty(cockcollects))
            return new CmdResVo(0,batchid);

        for (CreditCockcollect cock : cockcollects){
            String contractno=cock.getContractno();
            FiCreditcases creditcase=fiCreditcasesMapper.selectOne(new QueryWrapper<FiCreditcases>()
                    .eq("credit_acct",contractno)
            );
            if(creditcase==null){
                creditcase=new FiCreditcases();
                creditcase.setCrdt(new Date());
                creditcase.setCrusr($usrid);
                creditcase.setCustomernumber(cock.getCustNo());
                creditcase.setCreditAcct(contractno);
                creditcase.setProdtype("3"); //公鸡贷
                creditcase.setStatus(EnumFiCaseStatus.New.value);
                creditcase.setStatusdt(new Date());
                creditcase.setCcc(EnumFiCaseQueue.O.name);
                creditcase.setMdusr($usrid);
                creditcase.setMddt(new Date());
                creditcase.setBatchid(batchid);
                creditcase.setIndt(new Date());
                fiCreditcasesMapper.insert(creditcase);
            }
            else {
                creditcase.setMdusr($usrid);
                creditcase.setMddt(new Date());
                creditcase.setBatchid(batchid);
                creditcase.setIndt(new Date());
                fiCreditcasesMapper.update(creditcase, new UpdateWrapper<FiCreditcases>()
                        .lambda()
                        .eq(FiCreditcases::getCreditAcct, contractno)
                        .eq(FiCreditcases::getProdtype, "3")
                        .set(FiCreditcases::getRepaydt, null)
                        .set(FiCreditcases::getPenchgAcc, null)
                        .set(FiCreditcases::getOthExpense, null)
                        .set(FiCreditcases::getOdudPrin, cock.getDebttotal())
                        .set(FiCreditcases::getInterestFee, cock.getCrdfee())
                        .set(FiCreditcases::getOverPrin, cock.getCrdprin())
                        .set(FiCreditcases::getAssignusr, null)
                        .set(FiCreditcases::getAssignid, null)
                        .set(FiCreditcases::getAssigntype, null)
                        .set(FiCreditcases::getAssignbatchid, null)
                        .set(FiCreditcases::getSendtousr, null)
                        .set(FiCreditcases::getSendtodept, null)
                        .set(FiCreditcases::getDistributorid, null)
                        .set(FiCreditcases::getDistusr, null)
                        .set(FiCreditcases::getDistdt, null)
                        .set(FiCreditcases::getDistributetype, null)
                        .set(FiCreditcases::getDelayenddt, null)
                        .set(FiCreditcases::getDelaystatus, null)
                        .set(FiCreditcases::getLastcctaskid, null)
                        .set(FiCreditcases::getBindenddt, null)
                        .set(FiCreditcases::getRecycleusr, null)
                        .set(FiCreditcases::getRecycledsc, null)
                        .set(FiCreditcases::getRecycledt, null)
                        .set(FiCreditcases::getClosedt, null)
                        .set(FiCreditcases::getCloseusr, null)
                        .set(FiCreditcases::getRemark, null)
                        .set(FiCreditcases::getStopautodistenddt, null)
                        .set(FiCreditcases::getVisitusr, null)
                        .set(FiCreditcases::getLastccdt, null)
                        .set(FiCreditcases::getAppointdt, null)
                );
            }
        }

        return new CmdResVo(cockcollects.size(),batchid);
    }

    @Override
    @Transactional
    public CmdResVo DeleteFiCase(String $usrid, String batchid)
    {
        List<CreditCockcollect> cockcollects=baseMapper.selectList(
                new QueryWrapper<CreditCockcollect>()
                        .eq("batchid",batchid)
        );

        log.info("Cock.DeleteFiCase({}):count={}",batchid,cockcollects.size());

        if(JPubUtils.IsEmpty(cockcollects)) {
            fiImportHistMapper.delete(new QueryWrapper<FiImportHist>()
                    .eq("batchid", batchid)
            );
            return new CmdResVo(0, batchid);
        }

        baseMapper.delete(new QueryWrapper<CreditCockcollect>()
                .eq("batchid",batchid)
        );

        fiCreditcasesMapper.delete(new QueryWrapper<FiCreditcases>()
                .eq("batchid",batchid)
                .eq("prodtype","3")
        );

        conContactMapper.delete(new QueryWrapper<ConContact>()
                .eq("origin","20")
                .in("customernumber",String.format("(select cu.customernumber from con_customer cu where cu.origin='20' and cu.batchid='%s')",batchid))
        );

        conCustomerMapper.delete(new QueryWrapper<ConCustomer>()
                .eq("origin","20")
                .eq("batchid",batchid)
        );

        fiImportHistMapper.delete(new QueryWrapper<FiImportHist>()
                .eq("batchid",batchid)
        );

        log.info("Cock.DeleteFiCase({}):Ok",batchid);

        return new CmdResVo(cockcollects.size(),batchid);
    }

    @Override
    public CockCaseVo getCockCaseInfo(JSysUser user, Integer ficaseid)
    {
        String $usrid=user.getUsrid();
        String idstar= JUsrPerm.getPermission(user,JUsrPerm.DISSTAR_IDNO);

        CockCaseVo resVo=selectJoinOne(
                CockCaseVo .class,
                new MPJLambdaWrapper<CreditCockcollect>()
                        .selectAs("fun_getnames('BUSINESS.TYPE',fi.prodtype)",CockCaseVo::getProdtypedsc)
                        .selectAs("fun_getnames('CREDIT.ACCT.TYPE',t.acct_type)",CockCaseVo::getAcctTypedsc)
                        .selectAs("fi_hasStopCall(fi.creditcaseid,'CASE')", CockCaseVo::getIsstopcase)
                        .selectAs(String.format("fi_starSecu('%s','%s',cu.openacctcertno,'%s')",$usrid,JUsrPerm.DISSTAR_IDNO,idstar),CockCaseVo::getOpenacctcertno)
                        .innerJoin(FiCreditcases.class,"fi",FiCreditcases::getCreditAcct,CreditCockcollect::getContractno)
                        .leftJoin(ConCustomer.class,"cu",ConCustomer::getCustomernumber,FiCreditcases::getCustomernumber)
                        .selectAll(CreditCockcollect.class)
                        .select(ConCustomer::getCustname,ConCustomer::getCustomernumber)
                        .select(FiCreditcases::getCreditcaseid,FiCreditcases::getStatus,FiCreditcases::getCcc,FiCreditcases::getCreditAcct,FiCreditcases::getProdtype,
                                FiCreditcases::getIndt,FiCreditcases::getDistdt,FiCreditcases::getSendtodept,FiCreditcases::getSendtousr,FiCreditcases::getRepay,
                                FiCreditcases::getAppointdt,FiCreditcases::getLastccdt,FiCreditcases::getBindenddt)
                        .apply("fi_hasFiCaseView({0},fi.creditcaseid,fi.status,fi.sendtodept,fi.sendtousr)>0",$usrid)
                        .eq(FiCreditcases::getCreditcaseid,ficaseid)
        );
        List<ConCustomertag> custtags=conCustomertagMapper.selectJoinList(
                ConCustomertag.class,
                new MPJLambdaWrapper<ConCustomertag>()
                        .leftJoin(FiCreditcases.class,"fc",FiCreditcases::getCustomernumber,ConCustomertag::getCustid)
                        .selectAll(ConCustomertag.class)
                        .eq("fc.creditcaseid",ficaseid)
        );
        if(custtags!=null&&custtags.size()>0){
            List<String> tags=custtags.stream().map(ConCustomertag::getId).collect(Collectors.toList());
            resVo.setCusttags(tags);
        }

        return resVo;
    }
}




